#pragma once

#include "Query.h"
#include "Synonym.h"
#include "Result.h"
#include <queue>
#include <list>

/* ------------------------------------------------------------------------------------------
* A class that encapsulates an entire query.
* 
* Contains a list of:
*	Declarations: assign a, variable v, etc
*	Queries: Modies(a,v), Pattern a("_", "_"), etc - further separated into two lists
*	Results: Select a, etc
* ------------------------------------------------------------------------------------------- */

class CompleteQuery {
private:
	std::vector<Synonym*> declaration_parameters; /**< a vector of declared variables */
	std::vector<Query*> suchthat_queries; /**< a vector of such that queries */
	std::vector<Query*> pattern_queries; /**< a vector of pattern queries */
	Result *result; /**< The result parameter */

public:
	/** Constructor
	 * Initialise all CompleteQuery data structures etc.
	 */
	CompleteQuery();

	~CompleteQuery();

	/**
	 * Adds a condition of such that type query to the list
	 * @param query object of class Query to be added.
	 */
	void addSuchThatQuery(Query *query);

	/**
	 * Get all such that queries
	 * @return a vector of such that queries
	 */
	std::vector<Query*> getSuchThatQuery();

	/**
	 * Adds a condition of pattern type query to the list
	 * @param query object of class Query to be added.
	 */
	void addPatternQuery(Query *query);

	/**
	 * Get all pattern queries
	 * @return a vector of pattern queries
	 */
	std::vector<Query*> getPatternQuery();

	/**
	 * Adds a synonym to masterSynonymList.
	 * @param syn object of class Synonym to be added.
	 */
	void addDeclarationParameters(Synonym *syn);
	std::vector<Synonym*> getDeclarationParameters();

	/**
	 * Assign the value in the parameter to result
	 * @param res object of class Result to be set.
	 */
	void setResult(Result *res);

	/**
	 * Get the result parameter
	 * @return result parameter
	 */
	Result* getResult();
};